#include <stdint.h>

#include "freertos.h"
#include "task.h"

//空闲任务任务堆栈
static StackType_t IdleTaskStack[configMINIMAL_STACK_SIZE];
//空闲任务控制块
static StaticTask_t IdleTaskTCB;

//获取空闲任务地任务堆栈和任务控制块内存，因为本例程使用的
//静态内存，因此空闲任务的任务堆栈和任务控制块的内存就应该
//有用户来提供，FreeRTOS提供了接口函数vApplicationGetIdleTaskMemory()
//实现此函数即可。
//ppxIdleTaskTCBBuffer:任务控制块内存
//ppxIdleTaskStackBuffer:任务堆栈内存
//pulIdleTaskStackSize:任务堆栈大小
void vApplicationGetIdleTaskMemory(StaticTask_t **ppxIdleTaskTCBBuffer,
								   StackType_t **ppxIdleTaskStackBuffer,
								   uint32_t *pulIdleTaskStackSize)
{
	*ppxIdleTaskTCBBuffer = &IdleTaskTCB;
	*ppxIdleTaskStackBuffer = IdleTaskStack;
	*pulIdleTaskStackSize = configMINIMAL_STACK_SIZE;
}

//定时器服务任务堆栈
static StackType_t TimerTaskStack[configTIMER_TASK_STACK_DEPTH];
//定时器服务任务控制块
static StaticTask_t TimerTaskTCB;

//获取定时器服务任务的任务堆栈和任务控制块内存
//ppxTimerTaskTCBBuffer:任务控制块内存
//ppxTimerTaskStackBuffer:任务堆栈内存
//pulTimerTaskStackSize:任务堆栈大小
void vApplicationGetTimerTaskMemory(StaticTask_t **ppxTimerTaskTCBBuffer,
									StackType_t **ppxTimerTaskStackBuffer,
									uint32_t *pulTimerTaskStackSize)
{
	*ppxTimerTaskTCBBuffer = &TimerTaskTCB;
	*ppxTimerTaskStackBuffer = TimerTaskStack;
	*pulTimerTaskStackSize = configTIMER_TASK_STACK_DEPTH;
}

//任务优先级
#define START_TASK_PRIO		4
//任务堆栈大小
#define START_STK_SIZE 		128
//任务堆栈
StackType_t StartTaskStack[START_STK_SIZE];
//任务控制块
StaticTask_t StartTaskTCB;
//任务句柄
TaskHandle_t StartTask_Handler;
//任务函数
void start_task(void *pvParameters);

//开始任务任务函数
void start_task(void *pvParameters)
{
    //UBaseType_t uxHighWaterMark;
    //uxHighWaterMark = uxTaskGetStackHighWaterMark( NULL );
	taskENTER_CRITICAL();           //进入临界区
	
	task_led_init();
    //uxHighWaterMark = uxTaskGetStackHighWaterMark( NULL );
	//usb_task_init();
	gui_task_init();
	//task_key_init();
    //xPortGetFreeHeapSize();
	vTaskDelete(StartTask_Handler); //删除开始任务
	taskEXIT_CRITICAL();            //退出临界区
}

void freertos_start(void)
{
    StartTask_Handler = xTaskCreateStatic((TaskFunction_t)start_task,        //任务函数
                                      (const char *)"start_task",      //任务名称
                                      (uint32_t)START_STK_SIZE,    //任务堆栈大小
                                      (void *)NULL,              //传递给任务函数的参数
                                      (UBaseType_t)START_TASK_PRIO,   //任务优先级
                                      (StackType_t *)StartTaskStack,    //任务堆栈
                                      (StaticTask_t *)&StartTaskTCB);    //任务控制块
	vTaskStartScheduler();          //开启任务调度
}
